<?php
namespace slinks\extensions\amf\zend;


use slinks\core\DependencyInjection\ContainerAwareInterface;

use slinks\core\DependencyInjection\ContainerInterface;

/**
 * This class overrides the default Zend_Amf_Server 
 * to support exposing of php service with the RemoteMethod annotation.  
 * 
 * @author Navid Mitchell
 *
 */
class SlinksAmfServer extends \Zend_Amf_Server implements ContainerAwareInterface{ 
	
	/** 
	 * @var ContainerInterface $container
	 */
	private $container = null;

	/**
	 * @param boolean $proxyDoctrineCollections if true then all doctrine collections will be proxied to support lazy loading from the amf client
	 */
	function __construct($proxyDoctrineCollections=false){
		
		if($proxyDoctrineCollections){
			//FIXME: make sure this works wihout a hacked Zend_amf core. 
			\Zend_Amf_Parse_TypeLoader::addAdapter("Doctrine\\ORM\\PersistentCollection",new \slinks\extensions\amf\orm\PersistentCollectionAdapter());
		}
	}
	
	/**
	 * Adds a Service method as being available for use by remote clients. 
	 * 
	 * @param string $serviceName
	 * @param array $serviceMethodNames an array of method names that can be called for the given service.
	 */
	public function addRemoteMethods($serviceName,array $serviceMethodNames){
		
		$class = get_class($this->container->get($serviceName));
		
		$this->_classAllowed[$class] = true;
		$this->_methods[] = new ServiceAwareZendServerReflectionClass($serviceName, $serviceMethodNames, $this->container);
		
	}
	
	
	/**
	 * Must be called after all calls to addRemoteMethods. This allows needed post procesing to be performed. 
	 * I have elected to do this to improve performance versus doing this every time addRemoteMethods is called. 
	 * This is ok since this class shoul only be used by our extension.
	 */
	public function prepareServer(){
		parent::_buildDispatchTable();
	}
	
	
	/**
     * Sets the Container.
     *
     * @param ContainerInterface $container A ContainerInterface instance
     */
	function setContainer(ContainerInterface $container = null){
		$this->container = $container;
	}

}

